/**
  ******************************************************************************
  * @file    PWM.c 
  * @author  Dajin Li
  * @version V0.0.1
  * @date    08-08-2015 
  * @brief   This file contains  PWM output function 
  *				 
  *          
  ******************************************************************************
  * @attention
  *
  * <h2><center>&copy; KION(SZ) R&D Center
  *
  * Licensed under KION, (the "License");
  *
  ******************************************************************************
  */

/* Includes ------------------------------------------------------------------*/

#include "pwm.h"

//#include "var_tbl.h"
//#include "CAN1_J1939.h"
//#include "menu.h"
/* Global var ------------------------------------------------------------------*/
u32 pwm_period_value;
s32 traction_speed_raw1_temp;
s32 traction_speed_raw_temp;
s32 traction_speed_raw_hz;
s32 traction_speed_raw_hz_slewed;
s32 traction_speed_raw;
s16 eng_oil_level;
s16 eng_oil_temp;
/**
* @brief	Initializes PWM params to be used for lcd backlight and heater ctrl 
* @param	none
* @note     none
* @retval   none
*/
void LCD_PWM_Init(void)
{
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB, ENABLE);	//IO Port enable
    GPIO_InitTypeDef GPIO_InitStructure;
    GPIO_InitStructure.GPIO_Pin = GPIO_Pin_6;				//TIM4 CH1 connect to PB6 pin
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;			//GPIO_Mode_AF_PP 
    GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
    GPIO_Init(GPIOB,&GPIO_InitStructure);					//Initial PB6
	
    RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM4,ENABLE);		//Config Timer4
    TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure;
    TIM_TimeBaseStructure.TIM_Period = 100;
    TIM_TimeBaseStructure.TIM_Prescaler = 40; 
    TIM_TimeBaseStructure.TIM_ClockDivision = TIM_CKD_DIV1;
    TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up;//counter up
    TIM_TimeBaseStructure.TIM_RepetitionCounter = 0x0;
    TIM_TimeBaseInit(TIM4, &TIM_TimeBaseStructure);

    TIM_OCInitTypeDef TIM_OCInitStructure;
    TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM1;					//PWM1 Mode1
    TIM_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable;		//Compare output enable
    TIM_OCInitStructure.TIM_Pulse = 100; 									//Set duty
    TIM_OCInitStructure.TIM_OCPolarity = TIM_OCPolarity_High; 			//Output initial low
    TIM_OC1Init(TIM4, &TIM_OCInitStructure);							//Initial Timer 4
    TIM_OC1PreloadConfig(TIM4, TIM_OCPreload_Enable);					//Reload enable
    TIM_ARRPreloadConfig(TIM4, ENABLE);									

    TIM_Cmd(TIM4, ENABLE);												//enable time4
//	GPIO_InitStructure.GPIO_Pin = GPIO_Pin_6;
//	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
//	GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
//	GPIO_Init(GPIOB, &GPIO_InitStructure);
}

/**
* @brief	Initializes PWM params to be used for lcd backlight and heater ctrl 
* @param	none
* @note     none
* @retval   none
*/
void ADSample_Timer3_Init(void)
{
    TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure;    
    NVIC_InitTypeDef NVIC_InitStructure;     
    RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3,ENABLE);  
    TIM_TimeBaseStructure.TIM_Period = 249;
    TIM_TimeBaseStructure.TIM_Prescaler = 72;
    TIM_TimeBaseStructure.TIM_ClockDivision = 0;
    TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up;
    TIM_TimeBaseInit(TIM3,&TIM_TimeBaseStructure);     
    TIM_ITConfig(TIM3,TIM_IT_Update,ENABLE);    
    NVIC_InitStructure.NVIC_IRQChannel = TIM3_IRQn;    
    NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0;    
    NVIC_InitStructure.NVIC_IRQChannelSubPriority = 3;    
    NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;    
    NVIC_Init(&NVIC_InitStructure);     
    TIM_Cmd(TIM3,ENABLE);
}

/**
* @brief	This task updates the PWM outputs - LCD dimming and LCD heater drive.
* @param	none
* @note     none
* @retval   none
*/
 void PWM_task(void const *argument) 
{
    // Initialization
    task_status[UPDT_PWM_ID] = ALIVE;
    LCD_PWM_Init();
    
    // Tasks must run in an infinite loop:
    while (TRUE)
    {   
        if(Screen_Mode == MODE_Standby)
        {
            lcd_adjust_lighting(0, BK_LIGHT_OFF);
        }
        else
        {
            if(LCD_Bklight >= MAX_LCD_BKLEVEL)
			{
			    LCD_Bklight = MAX_LCD_BKLEVEL;
			}
            else if(LCD_Bklight <= 0)
            {
                LCD_Bklight = 0;
            }
            lcd_adjust_lighting(LCD_Bklight, BK_LIGHT_ON);
        }
        task_status[UPDT_PWM_ID] = ALIVE;
        osDelay(UPDT_PWM_ITV);
    }  // end while infinite loop
}  // end task_updt_PWM()			

void pwm_duty_adjust(int duty)
{
//	static int lcd_light_level;
	if((duty > 100) || (duty < 0))
	{
		return;
	}
    TIM_SetCompare1(TIM4, duty); 
//	if(lcd_light_level != duty)
//	{
//		lcd_light_level = duty;
//        TIM_SetCompare1(TIM4, lcd_light_level); 
//	}
}

void lcd_adjust_lighting(int bk_light_level, U8 bk_status)
{
	if(bk_status == BK_LIGHT_ON)
	{
		switch (bk_light_level)
		{
			case 0:	pwm_duty_adjust(15); break;
			case 1: pwm_duty_adjust(25); break;
			case 2: pwm_duty_adjust(35); break;
			case 3: pwm_duty_adjust(50); break;
			case 4: pwm_duty_adjust(80); break;
			case 5: pwm_duty_adjust(90); break;
			case 6:	pwm_duty_adjust(100); break;
			default: break;
		}
	}
	else if(bk_status == BK_LIGHT_OFF)
	{
		pwm_duty_adjust(0);
	}
}
